<?php

class BonusTask extends BuildTask {
    /**
     * @var bool $enabled If set to FALSE, keep it from showing in the list
     * and from being executable through URL or CLI.
     */
    protected $enabled = true;

    /**
     * @var string $title Shown in the overview on the {@link TaskRunner}
     * HTML or CLI interface. Should be short and concise, no HTML allowed.
     */
    protected $title = 'Bonus Task';

    /**
     * @var string $description Describe the implications the task has,
     * and the changes it makes. Accepts HTML formatting.
     */
    protected $description = 'Bonus Task';
	
	protected $batchid = null;
    protected $members = array();
	protected $sales = array();
	protected $matching = array();
	protected $pairing = array();
	protected $groups = array();
    
    private static $view_mode = true;

    public function init() {
        parent::init();
        
        $canAccess = (Director::isDev() || Director::is_cli() || Permission::check("ADMIN"));
        if(!$canAccess) return Security::permissionFailure($this);
    }
    
    /**
     * Implement this method in the task subclass to
     * execute via the TaskRunner
     */
    public function run($request) {
        increase_time_limit_to();
        increase_memory_limit_to('1024M');
        
        $start_time = $this->getStartTime();
        $date = date('Y-m-d', strtotime('-1 days'));
        DB::alteration_message('-----------------------------------------------', 'created');
        DB::alteration_message($date, 'created');
        DB::alteration_message('Start bonus task', 'created');
		try {
            DB::getConn()->transactionStart();
			$this->batchid = BonusBatch::get_batch_id_by_date($date);
			if($this->batchid){
				$this->groups = Group::get()->filter('IsDistributorGroup', 1)->sort('Sort')->map('ID', 'Code')->toArray();
				BonusBatch::get()->byID($this->batchid)->setField('IsClosed', 1)->setField('IsActive', 0)->setField('Date', $date)->write();
		
				$next_day = date('Y-m-d', strtotime($date .' +1 day'));
				BonusBatch::create()
				->setField('Code', date('Ymd', strtotime($next_day)))
				->setField('DateStart', $next_day)
				->setField('DateEnd', $next_day)
				->setField('Date', $next_day)
				->setField('IsActive', 1)
				->write();
				
		        $this->doProcessSummary($date);
				$this->doProcessUnilevel($date);
		        $this->doProcessInvestProgram($date);
				$this->doProcessMatching($date);
		        $this->doProcessPairing($date);
		        $this->doSaveSummary($date);
				$this->doRepurchase($date);
			}
			else{
				DB::alteration_message('Invalid batch id', 'deleted');
			}
			DB::getConn()->transactionEnd();
		}
        catch(ValidationException $e) {
			DB::getConn()->transactionRollback();
			SS_Log::log(new Exception(print_r($e->getMessage(), true)), SS_Log::NOTICE);
		}
        
        DB::alteration_message('End bonus task', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
    }
    
    protected function getStartTime(){
        $time = microtime();
        $time = explode(' ', $time);
        return $time[1] + $time[0];
    }
    
    protected function showProcessTime($start_time){
        $time = microtime();
        $time = explode(' ', $time);
        $time = $time[1] + $time[0];
        $total_time = round(($time - $start_time), 4);
        DB::alteration_message('Process Time - ' . $total_time . ' seconds', 'created');
    }

    protected function doProcessSummary($date){
        DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process bonus summary', 'created');
        $result = DB::query("SELECT '".$date."' AS Date, SUM(BFLPGBV) AS BFLPGBV, SUM(BFRPGBV) AS BFRPGBV, SUM(APSA) AS APSA, SUM(AADJPSA) AS AADJPSA, SUM(APBV) AS APBV, SUM(AADJPBV) AS AADJPBV, SUM(ASDSA) AS ASDSA, SUM(ASDBV) AS ASDBV, SUM(ASGBV) AS ASGBV, SUM(ALPGBV) AS ALPGBV, SUM(AADJLPGBV) AS AADJLPGBV, SUM(ARPGBV) AS ARPGBV, SUM(SPID) AS SPID, SUM(SLEFT) AS SLEFT, SUM(SRIGHT) AS SRIGHT, SUM(PPID) AS PPID, SUM(PLEFT) AS PLEFT, SUM(PRIGHT) AS PRIGHT, SUM(PPOS) AS PPOS, MemberID, (SELECT b.ID FROM Group_Members a inner join `Group` b on a.GroupID = b.ID WHERE a.MemberID = BonusSummary.MemberID AND b.IsDistributorGroup = 1 ORDER BY b.Sort DESC LIMIT 1) AS GroupID, (SELECT Status FROM Member WHERE ID = BonusSummary.MemberID LIMIT 1) AS Status, SUM(NoUnilevelPayout) AS NoUnilevelPayout, SUM(NoPairingPayout) AS NoPairingPayout, SUM(NoMatchingPayout) AS NoMatchingPayout, SUM(NoInvestPayout) AS NoInvestPayout, SUM(MBLV) AS MBLV FROM ((SELECT CFLPGBV AS BFLPGBV, CFRPGBV AS BFRPGBV, APSA AS APSA, AADJPSA AS AADJPSA, APBV AS APBV, AADJPBV AS AADJPBV, ASDSA AS ASDSA, ASDBV AS ASDBV, ASGBV AS ASGBV, ALPGBV AS ALPGBV, AADJLPGBV AS AADJLPGBV, ARPGBV AS ARPGBV, 0 AS SPID, 0 AS SLEFT, 0 AS SRIGHT, 0 AS PPID, 0 AS PLEFT, 0 AS PRIGHT, 0 AS PPOS, MemberID, 0 AS NoUnilevelPayout, 0 AS NoPairingPayout, 0 AS NoMatchingPayout, 0 AS NoInvestPayout, MBLV as MBLV FROM BonusSummary WHERE DATE(Date) = '".DB::query('SELECT MAX(Date) FROM BonusSummary')->value()."') UNION ALL (SELECT  0 AS BFLPGBV, 0 AS BFRPGBV, 0 AS APSA, 0 AS AADJPSA, 0 AS APBV, 0 AS AADJPBV, 0 AS ASDSA, 0 AS ASDBV, 0 AS ASGBV, 0 AS ALPGBV, 0 AS AADJLPGBV, 0 AS ARPGBV, b.ParentID AS SPID, b.NLeft AS SLEFT, b.NRight AS SRIGHT, c.ParentID AS PPID, c.NLeft AS PLEFT, c.NRight AS PRIGHT, c.NSeqno AS PPOS, a.ID AS MemberID, a.NoUnilevelPayout AS NoUnilevelPayout, a.NoPairingPayout AS NoPairingPayout, a.NoMatchingPayout AS NoMatchingPayout, a.NoInvestPayout AS NoInvestPayout, 0 AS MBLV FROM Member a INNER JOIN Sponsor b on a.ID = b.MemberID INNER JOIN Placement c on a.ID = c.MemberID GROUP BY a.ID)) AS BonusSummary GROUP BY MemberID ORDER BY PLEFT");

        foreach($result as $summary){
        	$summary['CPSA'] = 0;
        	$summary['CADJPSA'] = 0;
			$summary['CPBV'] = 0;
			$summary['CADJPBV'] = 0;
			$summary['CSDSA'] = 0;
            $summary['CSDBV'] = 0;
            $summary['CSGBV'] = 0;
            $summary['CLPGBV'] = 0;
            $summary['CADJLPGBV'] = 0;
            $summary['CRPGBV'] = 0;
            $summary['CADJRPGBV'] = 0;
            $summary['CFLPGBV'] = $summary['BFLPGBV'];
            $summary['CFRPGBV'] = $summary['BFRPGBV'];
            $summary['TLPGBV'] = $summary['BFLPGBV'];
            $summary['TRPGBV'] = $summary['BFRPGBV'];
            $summary['SDDL'] = 0;
            $summary['SGDL'] = ($summary['SRIGHT'] - $summary['SLEFT'] - 1) / 2;
            $summary['PGDL'] = ($summary['PRIGHT'] - $summary['PLEFT'] - 1) / 2;
            $summary['PLGDL'] = 0;
            $summary['PRGDL'] = 0;
            $summary['BS1'] = 0;
            $summary['BS2'] = 0;
            $summary['BS3'] = 0;
            $summary['BS4'] = 0;
            $summary['BS5'] = 0;
            if($summary['BFLPGBV'] > 0){
            	$this->pairing[$summary['MemberID']]['TLPGBV'] = $summary['BFLPGBV'];
            }
			if($summary['BFRPGBV'] > 0){
            	$this->pairing[$summary['MemberID']]['TRPGBV'] = $summary['BFRPGBV'];
            }
            if($summary['SPID']){
            	$this->members[$summary['SPID']]['SDDL'] += 1;
            	if(isset($this->groups[$this->members[$summary['SPID']]['GroupID']])){
            		if($this->groups[$this->members[$summary['SPID']]['GroupID']] == 'level1'){
            			$this->members[$summary['SPID']]['SDDL1K'] += 1;
					}
					else{
						$this->members[$summary['SPID']]['SDDL3K'] += 1;
					}
            	}
            }
            if($summary['PPID']){
            	if($summary['PPOS'] == 1){
            		$this->members[$summary['PPID']]['PLGDL'] += $summary['PGDL'];
            	} 
            	else if($summary['PPOS'] == 2){
            		$this->members[$summary['PPID']]['PRGDL'] += $summary['PGDL'];
            	}
            }
            $this->members[$summary['MemberID']] = $summary;
        }
        
		$result = DB::query("SELECT * FROM OrderPackage WHERE BatchID = '".$this->batchid."' AND Status = 'Fully Paid' AND (BV > 0 OR Price > 0)");
		foreach($result as $sales){
			$member =& $this->members[$sales['MemberID']];
			
			if($price = $sales['Price']){
				if($sales['PaymentReceiptID']){
					$member['CPSA'] += $price;
					$member['APSA'] += $price;
				}
				else{
					$member['CADJPSA'] += $price;
					$member['AADJPSA'] += $price;
				}
				if(isset($this->members[$member['SPID']]) && $sales['PaymentReceiptID']){
					$this->members[$member['SPID']]['CSDSA'] += $price;
					$this->members[$member['SPID']]['ASDSA'] += $price;
				}
			}
			
			if($bv = $sales['BV']){
				if($sales['PaymentReceiptID']){
					$member['CPBV'] += $bv;
					$member['APBV'] += $bv;
				}
				else{
					$member['CADJPBV'] += $bv;
					$member['AADJPBV'] += $bv;
				}
				
				if($sales['PaymentReceiptID']){
					$this->sales[$sales['ID']] = $sales;
				}
				
				if(isset($this->members[$member['SPID']]) && $sales['PaymentReceiptID']){
					$sponsor_id = $member['SPID'];
					$this->members[$sponsor_id]['CSDBV'] += $bv;
					$this->members[$sponsor_id]['ASDBV'] += $bv;
					
					while(isset($this->members[$sponsor_id])){
	                    $this->members[$sponsor_id]['CSGBV'] += $bv;
	                    $this->members[$sponsor_id]['ASGBV'] += $bv;
		                $sponsor_id = $this->members[$sponsor_id]['SPID'];
		            }
				}
				
				if($placement_id = $member['PPID']){
					$placement_position = $member['PPOS'];
	        		while(isset($this->members[$placement_id])){
						if($placement_position == 1){
							$this->members[$placement_id]['CLPGBV'] += $bv;
							$this->members[$placement_id]['CFLPGBV'] += $bv;
							$this->members[$placement_id]['ALPGBV'] += $bv;
							if(!$sales['PaymentReceiptID']){
								$this->members[$placement_id]['CADJLPGBV'] += $bv;
								$this->members[$placement_id]['AADJLPGBV'] += $bv;
							}
							$this->pairing[$placement_id]['TLPGBV'] = $this->members[$placement_id]['BFLPGBV'] + $this->members[$placement_id]['CLPGBV'];
						} else if($placement_position == 2){
							$this->members[$placement_id]['CRPGBV'] += $bv;
							$this->members[$placement_id]['CFRPGBV'] += $bv;
							$this->members[$placement_id]['ARPGBV'] += $bv;
							if(!$sales['PaymentReceiptID']){
								$this->members[$placement_id]['CADJRPGBV'] += $bv;
								$this->members[$placement_id]['AADJRPGBV'] += $bv;
							}
							$this->pairing[$placement_id]['TRPGBV'] = $this->members[$placement_id]['BFRPGBV'] + $this->members[$placement_id]['CRPGBV'];
						}
						
						$placement_position = $this->members[$placement_id]['PPOS'];
						$placement_id = $this->members[$placement_id]['PPID'];
					}
				}
			}
		}

        DB::alteration_message('End process bonus summary', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
    }

	protected function doProcessUnilevel($date){
		DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process unilevel program', 'created');
		$i = 0;
		foreach($this->sales as $sales){
			if($sales['BV'] > 0){
				$payout_table = Config::inst()->get('UnilevelBonus', 'payout_table');
				$remaining = max($payout_table);
				$last_percentage = 0;
				$level = 1;
				$parentid = $this->members[$sales['MemberID']]['SPID'];
				if($parentid && !$this->members[$parentid]['NoUnilevelPayout']){
					$code = isset($this->groups[$this->members[$parentid]['GroupID']]) ? $this->groups[$this->members[$parentid]['GroupID']] : '';
					if(isset($payout_table[$code]) && ($percentage = $payout_table[$code])){
						if($percentage > $last_percentage && $payout = $sales['BV'] * ($percentage - $last_percentage)){
							$current_percentage = $percentage - $last_percentage;
							$last_percentage = $percentage;
							$remaining -= $percentage;
							$unilevel_payout = UnilevelBonus::create()
							->setField('Percentage', $current_percentage)
							->setField('Level', $level)
							->setField('Credit', $payout)
							->setField('BatchID', $this->batchid)
							->setField('MemberID', $parentid)
							->setField('GroupID', $this->members[$parentid]['GroupID'])
							->setField('OrderPackageID', $sales['ID']);
							$unilevel_payout->write();
							$unilevel_payout->destroy();
		            		unset($unilevel_payout);
							$this->members[$parentid]['BS1'] += $payout;
							$level++;
							$i++;
						}
					}
				}
			}
		}
		
		DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End process unilevel program', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
	}

    protected function doProcessInvestProgram($date){
        DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process invest program', 'created');
        $i = 0;
        foreach(InvestProgram::get()->filter('NextPayout', $date)->filter('IsClosed', 0) as $program){
            if($program_payout = InvestProgramPayout::create_payout($program->ID, $this->batchid)){
            	if($program->OrderPackageID){
					$this->members[$program->MemberID]['BS2'] += $program_payout->Credit;
					
					$this->matching[$program->MemberID]['payout_id'][] = $program_payout->ID;
					if(isset($this->matching[$program->MemberID]['total_payout'])){
						$this->matching[$program->MemberID]['total_payout'] += $program_payout->Credit;
					}
					else {
						$this->matching[$program->MemberID]['total_payout'] = $program_payout->Credit;
					}
				}
				$program->destroy();
        		unset($program);
				$program_payout->destroy();
        		unset($program_payout);
				$i++;
            }
        }
        DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End process invest program', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
    }

	protected function doProcessMatching($date){
		DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process matching bonus', 'created');
		$i = 0;
		
		if(date('Ym', strtotime($date)) == '201503'){
			$payout_table = Config::inst()->get('MatchingBonus', 'payout_table_201503');
		}
		else{
			$payout_table = Config::inst()->get('MatchingBonus', 'payout_table');
		}

		$max_level = sizeof($payout_table);
		foreach($this->matching as $memberid => $data){
			$parentid = $this->members[$memberid]['SPID'];
			$level = 1;
			while($parentid && $max_level >= $level){
				if($this->members[$parentid]['NoMatchingPayout']){
					$parentid = $this->members[$parentid]['SPID'];
					$level++;
					continue;
				}
				$current_payout_table = isset($payout_table[$level]) ? $payout_table[$level] : '';
				$code = isset($this->groups[$this->members[$parentid]['GroupID']]) ? $this->groups[$this->members[$parentid]['GroupID']] : '';
				if($this->members[$parentid]['MBLV'] >= $level){
					$bool = ($current_payout_table && in_array($code, $current_payout_table['rank']) && ($percentage = $current_payout_table['percentage']));
				}
				else{
					$sddl = $this->members[$parentid]['SDDL1K'] + $this->members[$parentid]['SDDL3K'];
					$sddl3k = $this->members[$parentid]['SDDL1K'] < $current_payout_table['downline'] ? $this->members[$parentid]['SDDL3K'] + $this->members[$parentid]['SDDL1K'] - $current_payout_table['downline'] : $this->members[$parentid]['SDDL3K'];
					$bool = ($current_payout_table && in_array($code, $current_payout_table['rank']) && ($percentage = $current_payout_table['percentage']) && $sddl >= $current_payout_table['downline'] && $sddl3k >= $current_payout_table['downline3k']);
				}
				if($bool){
					if($level > $this->members[$parentid]['MBLV']){
						$this->members[$parentid]['MBLV'] = $level;
					}
					$payout = $data['total_payout'] * $percentage;
					if($payout > 0){
						$matching_payout = MatchingBonus::create()
						->setField('Percentage', $percentage)
						->setField('Downline1K', $this->members[$parentid]['SDDL1K'])
						->setField('Downline3K', $this->members[$parentid]['SDDL3K'])
						->setField('Level', $level)
						->setField('Credit', $payout)
						->setField('BatchID', $this->batchid)
						->setField('MemberID', $parentid)
						->setField('GroupID', $this->members[$parentid]['GroupID'])
						->setField('PassByID', $memberid);
						$matching_payout->write();
						$matching_payout->InvestProgramPayout()->addMany($data['payout_id']);
						$matching_payout->destroy();
	            		unset($matching_payout);
						$this->members[$parentid]['BS3'] += $payout;
						$i++;
					}
				}
				$parentid = $this->members[$parentid]['SPID'];
				$level++;
			}
		}
		DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End process matching bonus', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
	}
    
    protected function doProcessPairing($date){
        DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process pairing bonus', 'created');
        $i = 0;
		$payout_table = Config::inst()->get('PairingBonus', 'payout_table');
        foreach($this->pairing as $memberid => $data){
        	if($this->members[$memberid]['NoPairingPayout']) continue;
			if(isset($data['TLPGBV']) && isset($data['TRPGBV']) && $data['TLPGBV'] > 0 && $data['TRPGBV'] > 0){
				$code = isset($this->groups[$this->members[$memberid]['GroupID']]) ? $this->groups[$this->members[$memberid]['GroupID']] : '';
				$current_payout_table = $code && isset($payout_table[$code]) ? $payout_table[$code] : '';
				if($current_payout_table && $percentage = $current_payout_table['percentage']){
					$pair = ($data['TLPGBV'] > $data['TRPGBV']) ? $data['TRPGBV'] : $data['TLPGBV'];
					$payout = $pair * $percentage;
					if($payout >= $current_payout_table['max_payout']){
						$payout = $current_payout_table['max_payout'];
						if($this->members[$memberid]['CFLPGBV'] > $this->members[$memberid]['CFRPGBV']){
							$this->members[$memberid]['CFRPGBV'] = 0;
						}
						else{
							$this->members[$memberid]['CFLPGBV'] = 0;
						}
					}
					else {
						$this->members[$memberid]['CFLPGBV'] -= $pair;
						$this->members[$memberid]['CFRPGBV'] -= $pair;
					}

					$pairing_payout = PairingBonus::create()
					->setField('Percentage', $percentage)
					->setField('MaxPayout', $current_payout_table['max_payout'])
					->setField('BV', $pair)
					->setField('Credit', $payout)
					->setField('BatchID', $this->batchid)
					->setField('MemberID', $memberid)
					->setField('GroupID', $this->members[$memberid]['GroupID']);
					$pairing_payout->write();
					$pairing_payout->destroy();
            		unset($pairing_payout);
					$this->members[$memberid]['BS4'] += $payout;
					$i++;
				}
			}
			else{
				
			}
        }
        DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End process pairing bonus', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
    }
    
    protected function doSaveSummary($date){
        DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start save bonus summary', 'created');
        $i = 0;
        foreach($this->members as $memberid => $summary){
            $obj = BonusSummary::create()->update($summary)->setField('BatchID', $this->batchid);
            $id = $obj->write();
            $obj->destroy();
            unset($obj);
            $i++;
            DB::alteration_message('Save bonus summary record id - '.$id, 'created');
            DB::alteration_message('Bonus summary data - '.Convert::array2json($summary), 'created');
        }
		
		if(Director::isLive()){
			$query = new SQLQuery();
			$query = $query->setFrom('BonusSummary')->setOrderBy('Date DESC')->setLimit(3)->setGroupBy('BonusSummary.Date')->selectField('Date')->selectField('SUM(BonusSummary.CPSA)', 'CPSA')->selectField('SUM(BonusSummary.CPBV)', 'CPBV')->selectField('SUM(BonusSummary.BS1)', 'BS1')->selectField('SUM(BonusSummary.BS2)', 'BS2')->selectField('SUM(BonusSummary.BS3)', 'BS3')->selectField('SUM(BonusSummary.BS4)', 'BS4')->selectField('SUM(BonusSummary.BS5)', 'BS5');
			
			$content = '<table border="1" style="background-color:;border-collapse:collapse;border:1px solid #000000;color:#000000;width:100%" cellpadding="10" cellspacing="0">';
			$content .= sprintf('<tr><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th><th>%s</th></tr>', 'Date', 'Sales Amount', 'Sales BV', 'DRB', 'Fund Management Bonus', 'Matching Bonus', 'Pairing Bonus');
			foreach($query->execute() as $item){
				$content .= sprintf('<tr><td>%s</td><td>%s</td><td>%s</td><td>%s</td><td>%s</td><td>%s</td><td>%s</td></tr>', $item['Date'], $item['CPSA'], $item['CPBV'], $item['BS1'], $item['BS2'], $item['BS3'], $item['BS4']);
			}
			$content .= '</table>';
			$email = new Email(null, 'Hut.L <hut_25@yahoo.com>', 'Daily Bonus Summary', $content);
			$email->send();
		}
		
        DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End save bonus summary', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
    }

	function doRepurchase($date){
		DB::alteration_message('-----------------------------------------------', 'created');
        $start_time = $this->getStartTime();
        DB::alteration_message('Start process repurchase', 'created');
        $i = 0;
		
		$result = DB::query("SELECT a.ID FROM Member a INNER JOIN UpgradeAccountBalance b on a.ID = b.MemberID WHERE a.TotalPayout >= a.MaxPayout AND b.Balance >= a.MaxPayout AND a.MaxPayout > 0");
		foreach($result as $data){
			$member = Member::get()->byID($data['ID']);
			$package = Package::get()->filter('Type', 'Register')->find('UpgradeGroupID', $member->Rank()->ID);
			$price = $package ? $package->Prices()->first() : '';
			
			if($price && $price->Price > 0){
				$receipt = Receipt::create()
				->setField('TotalAmount', $price->Price)
				->setField('Currency', SiteCurrencyConfig::current_site_currency())
				->setField('MemberID', $member->ID)
				->updateTransactionType('REPURCHASE');
				
				$payment = UpgradePayment::create()->pendingPayment(array('Amount' => $price->Price, 'ReceiptID' => $receipt->ID));
				
				$billing_address = PackageBillingAddress::create()
				->setField('Name', $member->getName())
				->setField('Contact', $member->Mobile)
				->setField('Email', $member->Email)
				->setField('Address', $member->Address)
				->setField('Suburb', $member->Suburb)
				->setField('State', $member->State)
				->setField('Postcode', $member->Postcode)
				->setField('Country', $member->Country);
				$billing_address->write();
				
				$order = OrderPackage::create()
				->setField('Type', $package->Type)
				->setField('Title', $package->Title)
				->setField('Price', $price->Price)
				->setField('BV', $price->BV)
				->setField('PackageID', $package->ID)
				->setField('UpgradeGroupID', $package->UpgradeGroupID)
				->setField('BillingAddressID', $billing_address->ID)
				->setField('PaymentReceiptID', $receipt->ID)
				->setField('MemberID', $member->ID)
				->setField('PaidByID', $member->ID)
				->setField('SoldByID', $member->Sponsor()->ID);
				$order->write();
				
                if($payment->checkBalance()){
                    $payment->completePayment();
					$member->TotalPayout -= $member->MaxPayout;
					$member->write();
                }
			}
		}
		
		DB::alteration_message('Total '.$i.' records save', 'created');
        DB::alteration_message('End process repurchase', 'created');
        $this->showProcessTime($start_time);
        DB::alteration_message('-----------------------------------------------', 'created');
	}
}
?>